package com.lhl.jwt.security.providers;

import com.lhl.jwt.service.JwtUserDetailsService;
import com.lhl.jwt.token.JwtAuthenticationToken;
import com.lhl.jwt.token.MobileCodeAuthenticationToken;
import org.springframework.beans.factory.InitializingBean;
import org.springframework.security.authentication.AuthenticationProvider;
import org.springframework.security.core.Authentication;
import org.springframework.security.core.AuthenticationException;
import org.springframework.security.core.userdetails.UserDetails;
import org.springframework.util.Assert;


/**
 * jwt认证主要逻辑
 * @author zhangyf
 * @date 2019年8月16日
 */
public class MobileCodeAuthenticationProvider implements AuthenticationProvider, InitializingBean {

	private final JwtUserDetailsService userDetailsService;

	public MobileCodeAuthenticationProvider(JwtUserDetailsService userDetailsService) {
		this.userDetailsService = userDetailsService;
	}

	@Override
	public void afterPropertiesSet() throws Exception {
		Assert.notNull(this.userDetailsService, "A UserDetailsService must be set");
	}
	
	@Override
	public Authentication authenticate(Authentication authentication) throws AuthenticationException {
		Assert.isInstanceOf(MobileCodeAuthenticationToken.class, authentication, () -> {
			return "Only MobileCodeAuthenticationToken is supported";
		});
		MobileCodeAuthenticationToken  mobileCodeAuthenticationToken = (MobileCodeAuthenticationToken) authentication;
		UserDetails userDetails = userDetailsService.loadUserByMobile(mobileCodeAuthenticationToken.getPrincipal().toString());

		JwtAuthenticationToken token = new JwtAuthenticationToken(userDetails, null, userDetails.getAuthorities());
		return token;
	}

	@Override
	public boolean supports(Class<?> authentication) {
		return authentication.isAssignableFrom(MobileCodeAuthenticationToken.class);
	}
	
}
